package lg.minecraft.plugin.pokemonmenu.config;

import com.cobblemon.mod.common.api.abilities.Ability;
import com.cobblemon.mod.common.api.moves.Move;
import com.cobblemon.mod.common.pokeball.PokeBall;
import com.cobblemon.mod.common.pokemon.Gender;
import com.cobblemon.mod.common.pokemon.Pokemon;
import lg.minecraft.plugin.cobblemoncore.util.LocalizedName;
import lg.minecraft.plugin.cobblemoncore.util.PokemonDataCache;
import lg.minecraft.plugin.cobblemoncore.util.PokemonPlaceholderReplacer;
import lg.minecraft.plugin.cobblemoncore.util.PokemonUtil;
import lg.minecraft.plugin.library.config.LGBaseConfig;
import lg.minecraft.plugin.pokemonmenu.LGPokemonMenu;
import lg.minecraft.plugin.pokemonmenu.config.builder.*;
import lombok.Getter;
import org.bukkit.Material;
import org.bukkit.inventory.ItemFlag;
import org.bukkit.inventory.ItemStack;
import org.bukkit.inventory.meta.ItemMeta;

import java.util.HashMap;
import java.util.List;
import java.util.Map;

/**
 * @author langle__
 * @version 1.0
 */
public final class GuiItem extends LGBaseConfig {

    @Getter private ItemStack border;
    @Getter private ItemStack back;
    @Getter private ItemStack openPC;
    @Getter private ItemStack airPoke;
    @Getter private ItemStack showParty;
    @Getter private ItemStack showPC;
    @Getter private ItemStack edit;
    @Getter private ItemStack showPokemon;
    @Getter private ItemStack editForm;
    @Getter private ItemStack editMove;
    @Getter private ItemStack natureLonely;
    @Getter private ItemStack natureBrave;
    @Getter private ItemStack natureAdamant;
    @Getter private ItemStack natureNaughty;
    @Getter private ItemStack natureModest;
    @Getter private ItemStack natureMild;
    @Getter private ItemStack natureQuiet;
    @Getter private ItemStack natureRash;
    @Getter private ItemStack natureBold;
    @Getter private ItemStack natureRelaxed;
    @Getter private ItemStack natureImpish;
    @Getter private ItemStack natureLax;
    @Getter private ItemStack natureCalm;
    @Getter private ItemStack natureGentle;
    @Getter private ItemStack natureSassy;
    @Getter private ItemStack natureCareful;
    @Getter private ItemStack natureTimid;
    @Getter private ItemStack natureHasty;
    @Getter private ItemStack natureJolly;
    @Getter private ItemStack natureNaive;
    @Getter private ItemStack natureSerious;
    @Getter private ItemStack editMoveNoExist;
    @Getter private ItemStack editAirPoke;
    @Getter private ItemStack noPermission;
    @Getter private ItemStack infoMoveNoExist;
    @Getter private ItemStack cancelButton;
    @Getter private ItemStack functionNoEnable;
    @Getter private ItemStack noMoneyHeal;
    @Getter private ItemStack endBattle;
    @Getter private ItemStack ivsMax;
    @Getter private ItemStack ivsMin;
    @Getter private ItemStack evsMax;
    @Getter private ItemStack evsMin;
    @Getter private ItemStack noFUnction;
    @Getter private ItemStack noShowPartyPermission;
    @Getter private ItemStack noOpenWildPokemonPermission;
    @Getter private ItemStack noViewPlayerPokemonPermission;
    @Getter private ItemStack noMoneyHealPermission;
    @Getter private ItemStack noAutoHealPermission;
    @Getter private ItemStack noDisabledViewPermission;
    @Getter private ItemStack noEndBattlePermission;
    @Getter private ItemStack noEditModePermission;
    @Getter private ItemStack search;
    @Getter private ItemStack sort;
    @Getter private ItemStack sortLevel;
    @Getter private ItemStack sortIv;
    @Getter private ItemStack sortBase;
    @Getter private ItemStack sortType;
    @Getter private ItemStack sortGen;
    @Getter private ItemStack sortPokedex;
    @Getter private ItemStack inputEdit;

    private PlaceholderItemBuilder nextPageJump;
    private PlaceholderItemBuilder previousPageJump;
    private PlaceholderItemBuilder nextPage;
    private PlaceholderItemBuilder previousPage;
    private PlaceholderItemBuilder baseInfo;
    private PlaceholderItemBuilder abilityInfo;
    private PlaceholderItemBuilder miscInfo;
    private PlaceholderItemBuilder editShiny;
    private PlaceholderItemBuilder editLevel;
    private PlaceholderItemBuilder editScale;
    private PlaceholderItemBuilder editFriendship;
    private PlaceholderItemBuilder editIvAttack;
    private PlaceholderItemBuilder editIvSpecialAttack;
    private PlaceholderItemBuilder editIvDefence;
    private PlaceholderItemBuilder editIvSpecialDefence;
    private PlaceholderItemBuilder editIvHp;
    private PlaceholderItemBuilder editIvSpeed;
    private PlaceholderItemBuilder editEvAttack;
    private PlaceholderItemBuilder editEvSpecialAttack;
    private PlaceholderItemBuilder editEvDefence;
    private PlaceholderItemBuilder editEvSpecialDefence;
    private PlaceholderItemBuilder editEvHp;
    private PlaceholderItemBuilder editEvSpeed;
    private PlaceholderItemBuilder editGender;
    private PlaceholderItemBuilder editAbility;
    private PlaceholderItemBuilder editFormUnSelected;
    private PlaceholderItemBuilder editFormSelected;
    private PlaceholderItemBuilder editMoveExist;
    private PlaceholderItemBuilder infoMoveExist;
    private PlaceholderItemBuilder confirmButton;
    private PlaceholderItemBuilder moneyHeal;
    private PlaceholderItemBuilder editNick;
    private PlaceholderItemBuilder editNature;

    private DynamicMaterialItemBuilder openWildPokemon;
    private DynamicMaterialItemBuilder viewPlayerPokemon;
    private DynamicMaterialItemBuilder autoHeal;
    private DynamicMaterialItemBuilder disabledView;
    private DynamicMaterialItemBuilder editMode;

    private PokemonDisplayItemBuilder pokemon;
    private PokemonDisplayItemBuilder editPokemon;
    private PokemonDisplayItemBuilder partyPokemon;
    private PokemonDisplayItemBuilder pcPokemon;
    private PokemonDisplayItemBuilder partyPokemonNoToItem;
    private PokemonDisplayItemBuilder pcPokemonNoToItem;
    private PokemonDisplayItemBuilder selectPokemon;
    private PokemonDisplayItemBuilder removePokemon;
    private PokemonDisplayItemBuilder viewPokemon;

    private PokemonNBTItemBuilder itemPokemon;

    private PokemonBallItemBuilder editPokemonBall;

    private PokemonContextItemBuilder searchPokemon;

    public GuiItem() {
        super(LGPokemonMenu.getInstance(), "guiItem");
        init();
    }

    @Override
    public void load() {
        super.load();
        border = buildItemStack("border");
        back = buildItemStack("back");
        openPC = buildItemStack("open_pc");
        airPoke = buildItemStack("air_poke");
        showParty = buildItemStack("show_party");
        showPC = buildItemStack("show_pc");
        edit = buildItemStack("edit");
        showPokemon = buildItemStack("show_pokemon");
        editForm = buildItemStack("edit_form");
        editMove = buildItemStack("edit_move");
        natureLonely = buildItemStack("nature_lonely");
        natureBrave = buildItemStack("nature_brave");
        natureAdamant = buildItemStack("nature_adamant");
        natureNaughty = buildItemStack("nature_naughty");
        natureModest = buildItemStack("nature_modest");
        natureMild = buildItemStack("nature_mild");
        natureQuiet = buildItemStack("nature_quiet");
        natureRash = buildItemStack("nature_rash");
        natureBold = buildItemStack("nature_bold");
        natureRelaxed = buildItemStack("nature_relaxed");
        natureImpish = buildItemStack("nature_impish");
        natureLax = buildItemStack("nature_lax");
        natureCalm = buildItemStack("nature_calm");
        natureGentle = buildItemStack("nature_gentle");
        natureSassy = buildItemStack("nature_sassy");
        natureCareful = buildItemStack("nature_careful");
        natureTimid = buildItemStack("nature_timid");
        natureHasty = buildItemStack("nature_hasty");
        natureJolly = buildItemStack("nature_jolly");
        natureNaive = buildItemStack("nature_naive");
        natureSerious = buildItemStack("nature_serious");
        editMoveNoExist = buildItemStack("edit_move_no_exist");
        editAirPoke = buildItemStack("edit_air_poke");
        noPermission = buildItemStack("no_permission");
        infoMoveNoExist = buildItemStack("info_move_no_exist");
        cancelButton = buildItemStack("cancel_button");
        functionNoEnable = buildItemStack("function_no_enable");
        noMoneyHeal = buildItemStack("no_money_heal");
        endBattle = buildItemStack("end_battle");
        ivsMax = buildItemStack("ivs_max");
        ivsMin = buildItemStack("ivs_min");
        evsMax = buildItemStack("evs_max");
        evsMin = buildItemStack("evs_min");
        noFUnction = buildItemStack("no_function");
        noShowPartyPermission = buildItemStack("no_show_party_permission");
        noOpenWildPokemonPermission = buildItemStack("no_open_wild_pokemon_permission");
        noViewPlayerPokemonPermission = buildItemStack("no_view_player_pokemon_permission");
        noMoneyHealPermission = buildItemStack("no_money_heal_permission");
        noAutoHealPermission = buildItemStack("no_auto_heal_permission");
        noDisabledViewPermission = buildItemStack("no_disabled_view_permission");
        noEndBattlePermission = buildItemStack("no_end_battle_permission");
        noEditModePermission = buildItemStack("no_edit_mode_permission");
        search = buildItemStack("search");
        sort = buildItemStack("sort");
        sortLevel = buildItemStack("sort_level");
        sortIv = buildItemStack("sort_iv");
        sortBase = buildItemStack("sort_base");
        sortType = buildItemStack("sort_type");
        sortGen = buildItemStack("sort_gen");
        sortPokedex = buildItemStack("sort_pokedex");
        inputEdit = buildItemStack("input_edit");

        nextPageJump = createPlaceholderItemBuilder("next_page_jump");
        previousPageJump = createPlaceholderItemBuilder("previous_page_jump");
        nextPage = createPlaceholderItemBuilder("next_page");
        previousPage = createPlaceholderItemBuilder("previous_page");
        baseInfo = createPlaceholderItemBuilder("base_info");
        abilityInfo = createPlaceholderItemBuilder("ability_info");
        miscInfo = createPlaceholderItemBuilder("misc_info");
        editShiny = createPlaceholderItemBuilder("edit_shiny");
        editLevel = createPlaceholderItemBuilder("edit_level");
        editScale = createPlaceholderItemBuilder("edit_scale");
        editFriendship = createPlaceholderItemBuilder("edit_friendship");
        editIvAttack = createPlaceholderItemBuilder("edit_iv_attack");
        editIvSpecialAttack = createPlaceholderItemBuilder("edit_iv_special_attack");
        editIvDefence = createPlaceholderItemBuilder("edit_iv_defence");
        editIvSpecialDefence = createPlaceholderItemBuilder("edit_iv_special_defence");
        editIvHp = createPlaceholderItemBuilder("edit_iv_hp");
        editIvSpeed = createPlaceholderItemBuilder("edit_iv_speed");
        editEvAttack = createPlaceholderItemBuilder("edit_ev_attack");
        editEvSpecialAttack = createPlaceholderItemBuilder("edit_ev_special_attack");
        editEvDefence = createPlaceholderItemBuilder("edit_ev_defence");
        editEvSpecialDefence = createPlaceholderItemBuilder("edit_ev_special_defence");
        editEvHp = createPlaceholderItemBuilder("edit_ev_hp");
        editEvSpeed = createPlaceholderItemBuilder("edit_ev_speed");
        editGender = createPlaceholderItemBuilder("edit_gender");
        editAbility = createPlaceholderItemBuilder("edit_ability");
        editFormUnSelected = createPlaceholderItemBuilder("edit_form_unselected");
        editFormSelected = createPlaceholderItemBuilder("edit_form_selected");
        editMoveExist = createPlaceholderItemBuilder("edit_move_exist");
        infoMoveExist = createPlaceholderItemBuilder("info_move_exist");
        confirmButton = createPlaceholderItemBuilder("confirm_button");
        moneyHeal = createPlaceholderItemBuilder("money_heal");
        editNick = createPlaceholderItemBuilder("edit_nick");
        editNature = createPlaceholderItemBuilder("edit_nature");

        openWildPokemon = createDynamicMaterialItemBuilder("open_wild_pokemon");
        viewPlayerPokemon = createDynamicMaterialItemBuilder("view_player_party");
        autoHeal = createDynamicMaterialItemBuilder("auto_heal");
        disabledView = createDynamicMaterialItemBuilder("disabled_view");
        editMode = createDynamicMaterialItemBuilder("edit_mode");

        pokemon = createPokemonDisplayItemBuilder("pokemon");
        editPokemon = createPokemonDisplayItemBuilder("edit_pokemon");
        partyPokemon = createPokemonDisplayItemBuilder("party_pokemon");
        pcPokemon = createPokemonDisplayItemBuilder("pc_pokemon");
        partyPokemonNoToItem = createPokemonDisplayItemBuilder("party_pokemon_no_to_item");
        pcPokemonNoToItem = createPokemonDisplayItemBuilder("pc_pokemon_no_to_item");
        selectPokemon = createPokemonDisplayItemBuilder("select_pokemon");
        removePokemon = createPokemonDisplayItemBuilder("remove_pokemon");
        viewPokemon = createPokemonDisplayItemBuilder("view_pokemon");
        searchPokemon = createPokemonContextItemBuilder("search_pokemon");

        itemPokemon = createPokemonNBTItemBuilder("item_pokemon");

        editPokemonBall = createPokemonBallItemBuilder("edit_pokemon_ball");
    }

    public ItemStack getNextPageJump(int page, int maxPage) {
        Map<String, String> map = new HashMap<>();
        map.put("{page}", String.valueOf(page));
        map.put("{maxPage}", String.valueOf(maxPage));
        return nextPageJump.build(map);
    }

    public ItemStack getPreviousPageJump(int page, int maxPage) {
        Map<String, String> map = new HashMap<>();
        map.put("{page}", String.valueOf(page));
        map.put("{maxPage}", String.valueOf(maxPage));
        return previousPageJump.build(map);
    }

    public ItemStack getNextPage(int page, int maxPage) {
        Map<String, String> map = new HashMap<>();
        map.put("{page}", String.valueOf(page));
        map.put("{maxPage}", String.valueOf(maxPage));
        return nextPage.build(map);
    }

    public ItemStack getPreviousPage(int page, int maxPage) {
        Map<String, String> map = new HashMap<>();
        map.put("{page}", String.valueOf(page));
        map.put("{maxPage}", String.valueOf(maxPage));
        return previousPage.build(map);
    }

    public ItemStack getOpenWildPokemon(boolean v) {
        return openWildPokemon.build(Map.of("{value}", v ? PokemonUtil.yes : PokemonUtil.no), v);
    }

    public ItemStack getViewPlayerPokemon(boolean v) {
        return viewPlayerPokemon.build(Map.of("{value}", v ? PokemonUtil.yes : PokemonUtil.no), v);
    }

    public ItemStack getAutoHeal(boolean v) {
        return autoHeal.build(Map.of("{value}", v ? PokemonUtil.yes : PokemonUtil.no), v);
    }

    public ItemStack getDisabledView(boolean v) {
        return disabledView.build(Map.of("{value}", v ? PokemonUtil.yes : PokemonUtil.no), v);
    }

    public ItemStack getEditMode(boolean v) {
        return editMode.build(Map.of("{value}", v ? PokemonUtil.yes : PokemonUtil.no), v);
    }

    public ItemStack getEditShiny(boolean v) {
        return editShiny.build(Map.of("{value}", v ? PokemonUtil.yes : PokemonUtil.no));
    }

    public ItemStack getEditLevel(int v) {
        return editLevel.build(Map.of("{value}", String.valueOf(v)));
    }

    public ItemStack getEditScale(float v) {
        return editScale.build(Map.of("{value}", String.valueOf(v)));
    }

    public ItemStack getEditFriendship(int v) {
        return editFriendship.build(Map.of("{value}", String.valueOf(v)));
    }

    public ItemStack getEditIvAttack(int v) {
        return editIvAttack.build(Map.of("{value}", String.valueOf(v)));
    }

    public ItemStack getEditIvSpecialAttack(int v) {
        return editIvSpecialAttack.build(Map.of("{value}", String.valueOf(v)));
    }

    public ItemStack getEditIvDefence(int v) {
        return editIvDefence.build(Map.of("{value}", String.valueOf(v)));
    }

    public ItemStack getEditIvSpecialDefence(int v) {
        return editIvSpecialDefence.build(Map.of("{value}", String.valueOf(v)));
    }

    public ItemStack getEditIvHp(int v) {
        return editIvHp.build(Map.of("{value}", String.valueOf(v)));
    }

    public ItemStack getEditIvSpeed(int v) {
        return editIvSpeed.build(Map.of("{value}", String.valueOf(v)));
    }

    public ItemStack getEditEvAttack(int v, int r) {
        Map<String, String> map = new HashMap<>();
        map.put("{value}", String.valueOf(v));
        map.put("{remaining}", String.valueOf(r));
        return editEvAttack.build(map);
    }

    public ItemStack getEditEvSpecialAttack(int v, int r) {
        Map<String, String> map = new HashMap<>();
        map.put("{value}", String.valueOf(v));
        map.put("{remaining}", String.valueOf(r));
        return editEvSpecialAttack.build(map);
    }

    public ItemStack getEditEvDefence(int v, int r) {
        Map<String, String> map = new HashMap<>();
        map.put("{value}", String.valueOf(v));
        map.put("{remaining}", String.valueOf(r));
        return editEvDefence.build(map);
    }

    public ItemStack getEditEvSpecialDefence(int v, int r) {
        Map<String, String> map = new HashMap<>();
        map.put("{value}", String.valueOf(v));
        map.put("{remaining}", String.valueOf(r));
        return editEvSpecialDefence.build(map);
    }

    public ItemStack getEditEvHp(int v, int r) {
        Map<String, String> map = new HashMap<>();
        map.put("{value}", String.valueOf(v));
        map.put("{remaining}", String.valueOf(r));
        return editEvHp.build(map);
    }

    public ItemStack getEditEvSpeed(int v, int r) {
        Map<String, String> map = new HashMap<>();
        map.put("{value}", String.valueOf(v));
        map.put("{remaining}", String.valueOf(r));
        return editEvSpeed.build(map);
    }

    public ItemStack getEditFormUnSelected(String v) {
        return editFormUnSelected.build(Map.of("{value}", v));
    }

    public ItemStack getEditFormSelected(String v) {
        return editFormSelected.build(Map.of("{value}", v));
    }

    public ItemStack getConfirmButton(int v) {
        return confirmButton.build(Map.of("{value}", String.valueOf(v)));
    }

    public ItemStack getMoneyHeal(int v) {
        return moneyHeal.build(Map.of("{value}", String.valueOf(v)));
    }

    public ItemStack getEditNick(String v) {
        return editNick.build(Map.of("{value}", String.valueOf(v)));
    }

    public ItemStack getEditNature(String natureName, String natureType) {
        Map<String, String> map = new HashMap<>();
        map.put("{value}", natureName);
        map.put("{type}", natureType);
        return editNature.build(map);
    }

    public ItemStack getEditMoveExist(Move move) {
        return buildMoveItemStack(move, editMoveExist);
    }

    public ItemStack getInfoMoveExist(Move move) {
        return buildMoveItemStack(move, infoMoveExist);
    }

    private ItemStack buildMoveItemStack(Move move, PlaceholderItemBuilder builder) {
        Map<String, String> map = new HashMap<>();
        map.put("{move_name}", PokemonDataCache.getInstance().findMoveKey(move));
        map.put("{move_type}", move.getType().getDisplayName().getString());
        map.put("{move_damage_category}", move.getDamageCategory().getDisplayName().getString());
        double power = move.getPower();
        map.put("{move_power}", power > 0 ? String.valueOf(power) : "-");
        double accuracy = move.getAccuracy();
        map.put("{move_accuracy}", accuracy > 0 ? accuracy + "%" : "-");
        map.put("{move_pp}", String.valueOf(move.getCurrentPp()));
        map.put("{move_max_pp}", String.valueOf(move.getMaxPp()));
        map.put("{move_description}", move.getDescription().getString());
        return builder.build(map);
    }

    public ItemStack getEditGender(Gender gender) {
        return editGender.build(Map.of("{value}", LocalizedName.getGenderName(gender)));
    }

    public ItemStack getEditPokemonBall(PokeBall pokeBall) {
        return editPokemonBall.build(pokeBall);
    }

    public ItemStack getEditAbility(Ability ability) {
        return editAbility.build(Map.of("{value}", LocalizedName.getAbilityName(ability)));
    }

    public ItemStack getBaseInfo(Pokemon pokemon) {
        return baseInfo.build(PokemonPlaceholderReplacer.buildPokemonInfoPlaceholders(pokemon));
    }

    public ItemStack getAbilityInfo(Pokemon pokemon) {
        return abilityInfo.build(PokemonPlaceholderReplacer.buildPokemonInfoPlaceholders(pokemon));
    }

    public ItemStack getMiscInfo(Pokemon pokemon) {
        return miscInfo.build(PokemonPlaceholderReplacer.buildPokemonInfoPlaceholders(pokemon));
    }

    public ItemStack getEditPokemon(Pokemon pokemon) {
        return editPokemon.build(pokemon);
    }

    public ItemStack getPokemon(Pokemon pokemon) {
        return this.pokemon.build(pokemon);
    }

    public ItemStack getPartyPokemon(Pokemon pokemon) {
        return partyPokemon.build(pokemon);
    }

    public ItemStack getPcPokemon(Pokemon pokemon) {
        return pcPokemon.build(pokemon);
    }

    public ItemStack getPartyPokemonNoToItem(Pokemon pokemon) {
        return partyPokemonNoToItem.build(pokemon);
    }

    public ItemStack getPcPokemonNoToItem(Pokemon pokemon) {
        return pcPokemonNoToItem.build(pokemon);
    }

    public ItemStack getSelectPokemon(Pokemon pokemon) {
        return selectPokemon.build(pokemon);
    }

    public ItemStack getViewPokemon(Pokemon pokemon) {
        return viewPokemon.build(pokemon);
    }

    public ItemStack getSearchPokemon(Pokemon pokemon, int box, int slot) {
        Map<String, String> map = new HashMap<>();
        map.put("{box}", String.valueOf(box));
        map.put("{slot}", String.valueOf(slot));
        return searchPokemon.build(pokemon, map);
    }

    public ItemStack getRemovePokemon(Pokemon pokemon) {
        return removePokemon.build(pokemon);
    }

    public ItemStack getItemPokemon(Pokemon pokemon) {
        return itemPokemon.build(pokemon);
    }

    private PokemonContextItemBuilder createPokemonContextItemBuilder(String path) {
        String name = getString(path + ".name");
        List<String> list = getStringList(path + ".lore");
        return new PokemonContextItemBuilder(name, list);
    }

    private DynamicMaterialItemBuilder createDynamicMaterialItemBuilder(String path) {
        Material trueMaterial = getMaterial(path + ".enable_material");
        Material falseMaterial = getMaterial(path + ".disable_material");
        String name = getString(path + ".name");
        List<String> list = getStringList(path + ".lore");
        return new DynamicMaterialItemBuilder(trueMaterial, falseMaterial, name, list);
    }

    private PokemonBallItemBuilder createPokemonBallItemBuilder(String path) {
        List<String> list = getStringList(path + ".lore");
        return new PokemonBallItemBuilder(list);
    }

    private PokemonNBTItemBuilder createPokemonNBTItemBuilder(String path) {
        String name = getString(path + ".name");
        List<String> list = getStringList(path + ".lore");
        return new PokemonNBTItemBuilder(name, list);
    }

    private PokemonDisplayItemBuilder createPokemonDisplayItemBuilder(String path) {
        String name = getString(path + ".name");
        List<String> list = getStringList(path + ".lore");
        return new PokemonDisplayItemBuilder(name, list);
    }

    private EnchantedItemBuilder createEnchantedItemBuilder(String path) {
        Material material = getMaterial(path + ".material");
        String name = getString(path + ".name");
        List<String> list = getStringList(path + ".lore");
        return new EnchantedItemBuilder(material, name, list);
    }

    private PlaceholderItemBuilder createPlaceholderItemBuilder(String path) {
        Material material = getMaterial(path + ".material");
        String name = getString(path + ".name");
        List<String> list = getStringList(path + ".lore");
        return new PlaceholderItemBuilder(material, name, list);
    }

    private ItemStack buildItemStack(String path) {
        Material material = getMaterial(path + ".material");
        if (material == null) return null;
        ItemStack item = new ItemStack(material);
        ItemMeta meta = item.getItemMeta();
        if (meta != null) {
            meta.setDisplayName(getString(path + ".name"));
            meta.setLore(getStringList(path + ".lore"));
            meta.addItemFlags(ItemFlag.values());
            item.setItemMeta(meta);
        }
        return item;
    }

    public Material getMaterial(String path) {
        String text = getString(path);
        return text == null ? null : Material.getMaterial(text.toUpperCase());
    }

}
